﻿using System;
using System.Linq;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using Microsoft.WindowsMobile.PocketOutlook;
using Microsoft.WindowsMobile.PocketOutlook.MessageInterception;
using Microsoft.WindowsMobile.Status;
using Microsoft.WindowsCE.Forms;
using System.Runtime.InteropServices;

namespace Cryptophone2
{
    public partial class MainForm : Form
    {

        System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(MainForm));
        System.Windows.Forms.Timer timer = new System.Windows.Forms.Timer();

        protected MessageInterceptor smsInterceptor = null;
        // An ID which uniquiely identifies this application.
        protected readonly string appId = "Criptophone-SmsDeviceControl";

        SystemState _orientationWatcher;
        ScreenOrientation _orientationAtApplicationStart;
        ScreenOrientation _applicationOrientationOnDeactivate;
        bool _firstResizeEvent = true;
        ScreenOrientation _lastResizeOrientation = ScreenOrientation.Angle0;

        Thread awaitingForCall;
        Thread doingCall;
        Thread closingCall;
        private volatile bool _shouldStop;
        MakingCall formCall;
        int direction;
        string callIp;
        

        TcpListener tcpCallListener;
        Socket socketServer;
        TcpClient socketClient;

        NetworkStream networkStreamServer;
        NetworkStream networkStreamClient;
        System.IO.StreamWriter streamWriterServer;
        System.IO.StreamWriter streamWriterClient;
        System.IO.StreamReader streamReaderServer;
        System.IO.StreamReader streamReaderClient;

        public MainForm()
        {
            InitializeComponent();

            timer.Interval = (25) * (1);
            timer.Tick += new EventHandler(timer_Tick); // Everytime timer ticks, timer_Tick will be called  

            _shouldStop = false;

            awaitingForCall = new Thread(waitForCallThread);
            awaitingForCall.Start();

        }

        /// <summary>
        /// Click of "0" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox0_Click(object sender, EventArgs e)
        {
            pictureBox0.Image = Properties.Resources._0c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "0");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "1" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox1_Click(object sender, EventArgs e)
        {
            pictureBox1.Image = Properties.Resources._1c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "1");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;

        }

        /// <summary>
        /// Click of "2" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox2_Click(object sender, EventArgs e)
        {
            pictureBox2.Image = Properties.Resources._2c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "2");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "3" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox3_Click(object sender, EventArgs e)
        {
            pictureBox3.Image = Properties.Resources._3c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "3");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "4" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox4_Click(object sender, EventArgs e)
        {
            pictureBox4.Image = Properties.Resources._4c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "4");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "5" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox5_Click(object sender, EventArgs e)
        {
            pictureBox5.Image = Properties.Resources._5c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "5");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "6" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox6_Click(object sender, EventArgs e)
        {
            pictureBox6.Image = Properties.Resources._6c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "6");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "7" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox7_Click(object sender, EventArgs e)
        {
            pictureBox7.Image = Properties.Resources._7c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "7");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "8" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox8_Click(object sender, EventArgs e)
        {
            pictureBox8.Image = Properties.Resources._8c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "8");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "9" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBox9_Click(object sender, EventArgs e)
        {
            pictureBox9.Image = Properties.Resources._9c;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, "9");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "Close" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBoxClose_Click(object sender, EventArgs e)
        {
            pictureBoxClose.Image = Properties.Resources.chiudic;

            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "Delete" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBoxDel_Click(object sender, EventArgs e)
        {
            pictureBoxDel.Image = Properties.Resources.cancellac;
            String text = textBox_ip.Text;

            //Cancellare solo se c'è scritto qualcosa
            if (text.Length != 0)
            {
                // Caso in cui ci sia del testo selezionato
                if (textBox_ip.SelectionLength > 1)
                {
                    int pos = textBox_ip.SelectionStart;
                    text = text.Remove(textBox_ip.SelectionStart, textBox_ip.SelectionLength);
                    textBox_ip.Text = text;
                    textBox_ip.SelectionStart = pos;
                    textBox_ip.SelectionLength = 0;
                }
                else // Altrimenti cancello semplicemente l'ultimo carattere
                {
                    text = text.Remove(text.Length - 1, 1);
                    textBox_ip.Text = text;
                    textBox_ip.SelectionStart = textBox_ip.Text.Length;
                }
            }
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "." button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBoxDot_Click(object sender, EventArgs e)
        {
            pictureBoxDot.Image = Properties.Resources.puntoc;
            StringBuilder text = new StringBuilder();
            text.Append(textBox_ip.Text);
            int pos = textBox_ip.SelectionStart;
            text.Insert(pos, ".");
            textBox_ip.Text = text.ToString();
            textBox_ip.SelectionStart = pos + 1;
            timer.Enabled = true;
        }

        /// <summary>
        /// Click of "Call" button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void pictureBoxCall_Click(object sender, EventArgs e)
        {
            pictureBoxCall.Image = Properties.Resources.chiamac;
            timer.Enabled = true;

            //Take ip from textbox
            callIp = textBox_ip.Text;

            //Start doingCall Thread 
            doingCall = new Thread(doingCallThread);
            doingCall.Start();
        }

        /// <summary>
        /// Action for Call a Contact menu button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void menuItem_callcontact_Click(object sender, EventArgs e)
        {
            ContactList_ form = new ContactList_();

            //If dialog result is YES a contact to call is selected
            if (form.ShowDialog() == DialogResult.Yes)
            {
                String numberToSendSMS = form.GetNumber();

                //Take my ip address
                String MyIpAddress = GetMyIpAdress();

                //Send sms to partner of call
                SmsMessage message = new SmsMessage(numberToSendSMS, "Cryptophone: CALLREQUEST " + MyIpAddress);
                message.Send();

                string prompt = string.Format("SMS inviato. \nRichiesta di chiamata verso: {0} \nProprio IP: {1}", numberToSendSMS, MyIpAddress);
                MessageBox.Show(prompt);

                //Now sms is sent. Main socket is just ready to pick the call request.

            }
        }

        /// <summary>
        /// Action for Exit menu button
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void menuItemExit_Click(object sender, EventArgs e)
        {
            // Disable the message interceptor
            smsInterceptor.DisableApplicationLauncher();
            smsInterceptor.MessageReceived -= SmsInterceptor_MessageReceived;

            // Tidy up the resources used by the message interceptor
            if (smsInterceptor != null)
            {
                smsInterceptor.Dispose();
                smsInterceptor = null;
            }

            this.Dispose();
            this.Close();
        }

        /// <summary>
        /// Method called when MainForm is loading
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void MainForm_Load(object sender, EventArgs e)
        {
            // If the message interceptor is already enabled then
            // retrieve its current settings. Otherwise configure
            // a new instance. With 2nd parameter false application use
            // another thread for handler the sms
            if (MessageInterceptor.IsApplicationLauncherEnabled(appId))
            {
                smsInterceptor = new MessageInterceptor(appId, false);
                smsInterceptor.EnableApplicationLauncher(appId);
                smsInterceptor.MessageReceived += SmsInterceptor_MessageReceived;
            }
            else
            {
                // We want to intercept messages that begin with "Cryptophone:" within the
                // message body and delete these messages before they reach the
                // SMS inbox. With 2nd parameter false application use
                // another thread for handler the sms
                smsInterceptor = new MessageInterceptor(InterceptionAction.NotifyAndDelete, false);
                smsInterceptor.MessageCondition = new MessageCondition(MessageProperty.Body,
                    MessagePropertyComparisonType.StartsWith, "Cryptophone:");

                // Enable the message interceptor
                smsInterceptor.EnableApplicationLauncher(appId);
                smsInterceptor.MessageReceived += SmsInterceptor_MessageReceived;
            }

            // Set orientationWatcher handler
            _orientationWatcher = new SystemState(SystemProperty.DisplayRotation);
            _orientationWatcher.Changed += new ChangeEventHandler(OrientationWatcher_Changed);

            _orientationAtApplicationStart = SystemSettings.ScreenOrientation;

        }

        /// <summary>
        /// Method called on mainForm resize
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void MainForm_Resize(object sender, EventArgs e)
        {
            if (SystemSettings.ScreenOrientation != _lastResizeOrientation || _firstResizeEvent)
            {
                // Do whatever layout changes are necessary

                _lastResizeOrientation = SystemSettings.ScreenOrientation;
                _firstResizeEvent = false;
            }
        }

        /// <summary>
        /// Method called on mainForm activation
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void MainForm_Activated(object sender, EventArgs e)
        {
            SystemSettings.ScreenOrientation = _applicationOrientationOnDeactivate;
        }


        /// <summary>
        /// Method called on mainForm deactivation
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void MainForm_Deactivate(object sender, EventArgs e)
        {
            _applicationOrientationOnDeactivate = SystemSettings.ScreenOrientation;
            SystemSettings.ScreenOrientation = _orientationAtApplicationStart;
        }

        /// <summary>
        /// Method called on mainForm closing
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void MainForm_Closing(object sender, CancelEventArgs e)
        {

            //Release all resources

            awaitingForCall.Abort();

            socketServer.Shutdown(SocketShutdown.Both);
            networkStreamClient.Close();
            networkStreamServer.Close();
            streamReaderClient.Close();
            streamReaderServer.Close();
            streamWriterClient.Close();
            streamWriterServer.Close();


            socketServer.Close();
            socketClient.Close();
        }

        /// <summary>
        /// Method called when mainForm is closed
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void MainForm_Closed(object sender, EventArgs e)
        {
            // Disable the message interceptor
            smsInterceptor.DisableApplicationLauncher();
            smsInterceptor.MessageReceived -= SmsInterceptor_MessageReceived;

            // Tidy up the resources used by the message interceptor
            if (smsInterceptor != null)
            {
                smsInterceptor.Dispose();
                smsInterceptor = null;
            }
        }
        
        /// <summary>
        /// Handler method lunched when an sms is recived
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        void SmsInterceptor_MessageReceived(object sender, MessageInterceptorEventArgs e)
        {
            SmsMessage request = e.Message as SmsMessage;
            if (request != null)
            {

                // Look at the body of the SMS message to determine
                // which command we should execute
                String cmd = request.Body.Substring(13).Trim();
                String SIMnumber = request.From.Address.ToString();
                string ipNumber = "";

                int idx = cmd.IndexOf(" ");
                if (idx != -1)
                {
                    ipNumber = cmd.Substring(idx).Trim();
                    cmd = cmd.Substring(0, idx).Trim();
                }

                switch (cmd)
                {
                    case "CALLREQUEST":
                        // Launch the calling incoming form

                        VoiceCall voiceForm = new VoiceCall(SIMnumber);

                        if (voiceForm.ShowDialog() == DialogResult.Yes)
                        {
                            //Set the ip to call
                            callIp = ipNumber;

                            //Start doingCall thread
                            doingCall = new Thread(doingCallThread);
                            doingCall.Start();
                        }

                        break;

                    default:

                        break;
                }
            }
        }

        /// <summary>
        /// Handler method lunched when orientation is changed
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="args"></param>
        void OrientationWatcher_Changed(object sender, ChangeEventArgs args)
        {
            int newOrientation = (int)args.NewValue;
            // Do whatever layout changes are necessary
            if (SystemSettings.ScreenOrientation == ScreenOrientation.Angle0)
            {
                pictureBox_BackGround.Image = Properties.Resources.background;
                pictureBox_BackGround.Size = new System.Drawing.Size(240, 400);

                //Positioning buttons portait mode
                // TODO: Change here 
            }
            if (SystemSettings.ScreenOrientation == ScreenOrientation.Angle90)
            {
                
                pictureBox_BackGround.Image = Properties.Resources.background_landscape;
                pictureBox_BackGround.Size = new System.Drawing.Size(320, 188);

                //Positioning buttons landscape mode
                //TODO: Change here
               

               /* pictureBox0.Location = new System.Drawing.Point(255, 139);
                pictureBox1.Location = new System.Drawing.Point(73, 47);
                pictureBox2.Location = new System.Drawing.Point(132, 47);
                pictureBox3.Location = new System.Drawing.Point(191, 47);
                pictureBox4.Location = new System.Drawing.Point(73, 93);
                pictureBox5.Location = new System.Drawing.Point(132, 93);
                pictureBox6.Location = new System.Drawing.Point(191, 93);
                pictureBox7.Location = new System.Drawing.Point(73, 139);
                pictureBox8.Location = new System.Drawing.Point(132, 139);
                pictureBox9.Location = new System.Drawing.Point(191, 139);
                pictureBoxCall.Location = new System.Drawing.Point(8, 47);
                pictureBoxClose.Location = new System.Drawing.Point(8, 139);
                pictureBoxDel.Location = new System.Drawing.Point(271, 7);
                pictureBoxDot.Location = new System.Drawing.Point(271, 103);
                textBox_ip.Location = new System.Drawing.Point(8, 7);
                textBox_ip.Size = new System.Drawing.Size(242, 29);*/
            }
        }

        /// <summary>
        /// Method lunched when timer ends. (Used for button effects)
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        void timer_Tick(object sender, EventArgs e)
        {
            timer.Enabled = false;

            this.pictureBox0.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox0.Image")));
            this.pictureBox1.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox1.Image")));
            this.pictureBox2.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox2.Image")));
            this.pictureBox3.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox3.Image")));
            this.pictureBox4.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox4.Image")));
            this.pictureBox5.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox5.Image")));
            this.pictureBox6.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox6.Image")));
            this.pictureBox7.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox7.Image")));
            this.pictureBox8.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox8.Image")));
            this.pictureBox9.Image = ((System.Drawing.Image)(resources.GetObject("pictureBox9.Image")));
            this.pictureBoxCall.Image = ((System.Drawing.Image)(resources.GetObject("pictureBoxCall.Image")));
            this.pictureBoxClose.Image = ((System.Drawing.Image)(resources.GetObject("pictureBoxClose.Image")));
            this.pictureBoxDel.Image = ((System.Drawing.Image)(resources.GetObject("pictureBoxDel.Image")));
            this.pictureBoxDot.Image = ((System.Drawing.Image)(resources.GetObject("pictureBoxDot.Image")));
        }

        /// <summary>
        /// Get ip Address
        /// </summary>
        /// <returns>Actial ip address</returns>
        String GetMyIpAdress()
        {
            IPHostEntry host;
            String localIP = "?";
            host = Dns.GetHostEntry(Dns.GetHostName());
            foreach (IPAddress ip in host.AddressList)
            {
                if (ip.AddressFamily.ToString() == "InterNetwork")
                {
                    localIP = ip.ToString();
                }
            }
            return localIP;
        }

        /// <summary>
        /// Main thread that keeping the incoming calls
        /// </summary>
        void waitForCallThread()
        {
            //Create a ServerSide Socket on port 3666
            IPAddress localAddr = IPAddress.Any;
            tcpCallListener = new TcpListener(localAddr, 3666);
            tcpCallListener.Start();

            try
            {

                while (!_shouldStop)
                {
                    //Accept a new call
                    socketServer = tcpCallListener.AcceptSocket();

                    if (socketServer.Connected)
                    {
                        //Have an incoming call. Must use direction 1
                        
                        // Get ip address of client
                        string Ip = ((IPEndPoint)socketServer.RemoteEndPoint).Address.ToString();

                        //Start stream structures
                        networkStreamServer = new NetworkStream(socketServer);
                        streamWriterServer = new System.IO.StreamWriter(networkStreamServer);
                        streamReaderServer = new System.IO.StreamReader(networkStreamServer);
                        string buffer = "";

                        // Form used to accept or refuse the call
                        VoiceCall voiceForm = new VoiceCall(Ip);
                        
                        if (voiceForm.ShowDialog() == DialogResult.Yes)
                        {
                            // Send "accepted" message to Client
                            buffer = "accepted";
                            streamWriterServer.WriteLine(buffer);
                            streamWriterServer.Flush();

                            // And start Call Form
                            formCall = new MakingCall(Ip, 0);

                            direction = 0;

                            //Start closingCall thred (listen for STOP command)
                            closingCall = new Thread(waitForCloseCallThread);
                            closingCall.Start();
                            
                            if (formCall.ShowDialog() == DialogResult.Abort)
                            {
                                //User abort the call. Send STOP command
                                buffer = "STOP";
                                streamWriterServer.WriteLine(buffer);
                                streamWriterServer.Flush();
                            }

                            //Call is terminated. So we send a command 
                            //to stop closingCall thread of Client
                            buffer = "terminated";
                            streamWriterServer.WriteLine(buffer);
                            streamWriterServer.Flush();

                            //Wait closingCall end.
                            closingCall.Join();
                            
                            formCall.Dispose();
                        }
                        else
                        {
                            // Send to client "refused" command
                            buffer = "refused";
                            streamWriterServer.WriteLine(buffer);
                            streamWriterServer.Flush();
                            
                        }

                        // Release of resources
                        voiceForm.Dispose();
                        streamReaderServer.Close();
                        streamWriterServer.Close();
                        networkStreamServer.Close();
                        socketServer.Shutdown(SocketShutdown.Both);
                        socketServer.Close();
                    }
                }
            }
            catch (System.IO.IOException ec)
            {
                Console.WriteLine("IOException: {0}", ec);
            }
        }

        /// <summary>
        /// Thread used to listen the STOP commando from call partner (after Abort command)
        /// </summary>
        void waitForCloseCallThread()
        {
            // 0 -> socketServer, 1 -> socketClient
            string buffer;

            while (true)
            {
                try
                {
                    if (direction == 0)
                        buffer = streamReaderServer.ReadLine();
                    else
                        buffer = streamReaderClient.ReadLine();

                    if (buffer.Equals("STOP"))
                    {
                        //Abort the call
                        formCall.setChiudi();
                    }

                    if (buffer.Equals("terminated"))
                        break; //exit from thread
                }
                catch (System.IO.IOException ec)
                {
                    Console.WriteLine("IOException: {0}", ec);
                    break;
                }
            }    
        }
       

        /// <summary>
        /// Thread used to start a new call
        /// </summary>
        private void doingCallThread()
        {
            string buffer = "";
            try
            {
                //connect to server
                socketClient = new TcpClient(callIp, 3666);

                //start stream structure
                networkStreamClient = socketClient.GetStream();
                streamReaderClient = new System.IO.StreamReader(networkStreamClient);
                streamWriterClient = new System.IO.StreamWriter(networkStreamClient);

                //Read call partner response
                buffer = streamReaderClient.ReadLine();

                if (buffer.Equals("refused"))
                {
                    //Call was refused
                    MessageBox.Show("La chiamata è stata rifiutata");
                }
                else
                {
                    direction = 1;

                    //Start closingCall thread
                    closingCall = new Thread(waitForCloseCallThread);
                    closingCall.Start();

                    //Start call form (direzione = 1)
                    formCall = new MakingCall(callIp, 1);

                    if (formCall.ShowDialog() == DialogResult.Abort)
                    {
                        //Call was aborted. Send a STOP command
                        buffer = "STOP";
                        streamWriterClient.WriteLine(buffer);
                        streamWriterClient.Flush();
                    }

                    // Call is terminated. Send a command to end 
                    // closingCall thread of call partner
                    buffer = "terminated";
                    streamWriterClient.WriteLine(buffer);
                    streamWriterClient.Flush();

                    //wait closingCall Thread end.
                    closingCall.Join();

                    formCall.Dispose();
                }

                //Release or resources
                streamReaderClient.Close();
                streamWriterClient.Close();
                networkStreamClient.Close();
                socketClient.Client.Shutdown(SocketShutdown.Both);
                socketClient.Close();
            }
            catch (System.IO.IOException ec)
            {
                Console.WriteLine("IOException: {0}", ec);
            }
            catch (ObjectDisposedException eb)
            {
                Console.WriteLine("ObjectDisposedException: {0}", eb);
            }
            catch (ArgumentNullException exc)
            {
                Console.WriteLine("ArgumentNullException: {0}", exc);
            }
            catch (SocketException exc2)
            {
                Console.WriteLine("SocketException: {0}", exc2);
            }
        }
    }
}